package com.cw.jeeyt.service.impl.system;

import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.alibaba.fastjson.JSON;
import com.cw.jeeyt.common.Constants;
import com.cw.jeeyt.service.bo.system.SystemDictBo;
import com.cw.jeeyt.service.bo.system.SystemDictCacheBo;
import com.cw.jeeyt.core.util.SessionUtil;
import com.cw.jeeyt.dao.intf.system.SystemDictDao;
import com.cw.jeeyt.dao.model.system.SystemDictDo;
import com.cw.jeeyt.service.converter.system.SystemDictConverter;
import com.cw.jeeyt.service.intf.system.SystemDictService;
import com.cw.lang.cache.Cache;
import com.cw.lang.common.utils.CollectionUtil;
import com.cw.lang.common.utils.StringUtil;
import com.cw.lang.mybatis.dto.PageInfo;
import com.cw.lang.common.utils.SequenceTool;

/**
 * 数据字典业务实现类
 *
 * @author chenw
 * @version 1.0.0
 */
@Service
public class SystemDictServiceImpl implements SystemDictService {

    private static final Logger logger = LoggerFactory.getLogger(SystemDictServiceImpl.class);
    @Autowired
    private SystemDictDao systemDictDao;
    @Autowired
    private Cache<String,String> dictCache;
    /**
     * 新增SystemDict
     *
     * @param systemDictBo
     * @return
     */
    @Transactional(rollbackFor = Exception.class)
    @Override
    public String insertSystemDict(SystemDictBo systemDictBo) {

        if (systemDictBo == null) {
            logger.error("数据字典信息为空");
            return null;
        }
        SystemDictDo systemDict = SystemDictConverter.bo2Do(systemDictBo);
        String itemCode = systemDict.getItemCode();
        String itemName = systemDict.getItemName();
        String itemValue = systemDict.getItemValue();
        if (StringUtils.isNotEmpty(itemCode)) {
            systemDict.setItemCode(itemCode.replace(" ", ""));
        }
        if (StringUtils.isNotEmpty(itemName)) {
            systemDict.setItemName(itemName.replace(" ", ""));
        }
        if (StringUtils.isNotEmpty(itemValue)) {
            systemDict.setItemValue(itemValue.replace(" ", ""));
        }
        systemDict.setId(SequenceTool.nextId());
        systemDict.setCreateBy(SessionUtil.getSessionUserId());
        systemDict.setCreateDate(new Date());
        systemDict.setUpdateBy(SessionUtil.getSessionUserId());
        systemDict.setUpdateDate(new Date());
        systemDictDao.insertSystemDict(systemDict);
        dictCache.delete(Constants.DICT_LIST_CACHE);
        return systemDict.getId();
    }

    /**
     * 更新SystemDict信息
     *
     * @param systemDictBo
     */
    @Transactional(rollbackFor = Exception.class)
    @Override
    public void updateSystemDict(SystemDictBo systemDictBo) {

        if (systemDictBo == null) {
            logger.error("数据字典信息为空");
            return;
        }
        SystemDictDo systemDict = SystemDictConverter.bo2Do(systemDictBo);
        String itemCode = systemDict.getItemCode();
        String itemName = systemDict.getItemName();
        String itemValue = systemDict.getItemValue();
        if (StringUtils.isNotEmpty(itemCode)) {
            systemDict.setItemCode(itemCode.replace(" ", ""));
        }
        if (StringUtils.isNotEmpty(itemName)) {
            systemDict.setItemName(itemName.replace(" ", ""));
        }
        if (StringUtils.isNotEmpty(itemValue)) {
            systemDict.setItemValue(itemValue.replace(" ", ""));
        }
        systemDict.setUpdateBy(SessionUtil.getSessionUserId());
        systemDict.setUpdateDate(new Date());
        systemDictDao.updateSystemDict(systemDict);
        dictCache.delete(Constants.DICT_LIST_CACHE);
    }

    /**
     * 删除SystemDict
     *
     * @param systemDictBo
     */
    @Transactional(rollbackFor = Exception.class)
    @Override
    public void deleteSystemDict(SystemDictBo systemDictBo) {
        if (systemDictBo == null) {
            logger.error("数据字典信息为空");
            return;
        }
        systemDictDao.deleteSystemDict(SystemDictConverter.bo2Do(systemDictBo));
        dictCache.delete(Constants.DICT_LIST_CACHE);
    }

    /**
     * 分页查询SystemDict
     *
     * @param systemDictBo
     * @param startNum
     * @param pageSize
     * @return
     * @throws Exception
     */
    @Override
    public PageInfo<SystemDictCacheBo> queryByPage(SystemDictBo systemDictBo, Integer startNum, Integer pageSize)
    throws Exception {

        PageInfo<SystemDictDo> pageInfo = systemDictDao.queryByPage(SystemDictConverter.bo2Do(systemDictBo), startNum,
            pageSize);
        PageInfo<SystemDictCacheBo> pageResult = new PageInfo<>(pageInfo,
            SystemDictConverter.doList2CacheBoList(pageInfo.getList()));
        if (CollectionUtil.isNotEmpty(pageResult.getList())) {
            pageResult.getList()
                .forEach(input -> {
                    try {
                        input.setChildList(this.getItemDictListByParentId(systemDictBo.getId()));
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                });
        }
        return pageResult;
    }

    /**
     * 根据主键查询SystemDict信息
     *
     * @param id
     * @return
     */
    @Override
    public SystemDictBo getSystemDictById(String id) {
        if(StringUtil.isBlank(id)){
            return null;
        }
        List<SystemDictCacheBo> systemDictBos = queryDictListByCache();
        if(CollectionUtil.isNotEmpty(systemDictBos)){
            SystemDictCacheBo cacheBo = systemDictBos.stream().filter(input -> input.getId().equals(id)).findFirst().get();
            SystemDictBo systemDictBo = new SystemDictBo();
            BeanUtils.copyProperties(cacheBo,systemDictBo);
            return systemDictBo;
        }
        return null;
    }

    @Override
    public SystemDictCacheBo getSystemDictByItemCode(String itemCode) {
        if(StringUtil.isEmpty(itemCode)){
            return null;
        }
        List<SystemDictCacheBo> systemDictBos = queryDictListByCache();
        if(CollectionUtil.isNotEmpty(systemDictBos)){
            List<SystemDictCacheBo> dictBos = systemDictBos.stream().filter(dict->itemCode.equals(dict.getItemCode())).collect(Collectors.toList());
            return CollectionUtil.isNotEmpty(dictBos) ? dictBos.get(0) : null;
        }
        return null;
    }

    /**
     * 根据父id查询数据字典子项
     *
     * @param parentId 父id
     * @return
     */
    @Override
    public List<SystemDictCacheBo> getItemDictListByParentId(String parentId) {
        if(StringUtil.isBlank(parentId)){
            return null;
        }
        List<SystemDictCacheBo> systemDictBos = queryDictListByCache();
        if(CollectionUtil.isNotEmpty(systemDictBos)){
            return systemDictBos.stream().filter(dict->parentId.equals(dict.getParentId())).collect(Collectors.toList());
        }
        return null;
    }

    /**
     * 根据字典名称、字典编码查询数据字典信息
     *
     * @param itemCode 字典编码
     * @param itemName 字典名称
     */
    @Override
    public SystemDictCacheBo getSystemDictByItemName(String itemCode, String itemName) {
        SystemDictCacheBo systemDictBo = new SystemDictCacheBo();
        SystemDictDo systemDictDo = systemDictDao.getSystemDictByItemName(itemCode, itemName);
        BeanUtils.copyProperties(systemDictDo,systemDictBo);
        if (systemDictBo == null) {
            return null;
        }
        systemDictBo.setChildList(this.getItemDictListByParentId(systemDictBo.getId()));
        return systemDictBo;
    }

    /**
     * 根据字典值、字典编码查询数据字典信息
     *
     * @param itemValue 字典值
     * @param itemCode 字典编码
     */
    @Override
    public SystemDictCacheBo getSystemDictByItemValue(String itemCode, String itemValue) {
        SystemDictCacheBo systemDictBo = SystemDictConverter.do2CacheBo(
            systemDictDao.getSystemDictByItemValue(itemCode, itemValue));
        if (systemDictBo == null) {
            return null;
        }
        systemDictBo.setChildList(this.getItemDictListByParentId(systemDictBo.getId()));
        return systemDictBo;
    }

    @Override
    public SystemDictCacheBo geSystemDictInfo(String itemCode, String itemName, String itemValue) {
        List<SystemDictCacheBo> dictBos = queryDictListByCache();
        if(CollectionUtil.isNotEmpty(dictBos)){
           for(SystemDictCacheBo dictBo : dictBos){
               if(StringUtil.isNotBlank(itemCode) && itemCode.equals(dictBo.getItemCode())){
                   return dictBo;
               }
               if(StringUtil.isNotBlank(itemName) && itemName.equals(dictBo.getItemName())){
                   return dictBo;
               }
               if(StringUtil.isNotBlank(itemValue) && itemValue.equals(dictBo.getItemValue())){
                   return dictBo;
               }
           }
        }
        return null;
    }

    @Override
    public ArrayList<SystemDictCacheBo> querySystemDictList() {
        ArrayList<SystemDictCacheBo> dictBos = SystemDictConverter.doList2CacheBoList(systemDictDao.querySystemDictList());
        if (CollectionUtil.isNotEmpty(dictBos)) {
            dictBos.forEach(input -> {
                String parentId = input.getParentId();
                if (StringUtils.isEmpty(parentId)) {
                    ArrayList<SystemDictCacheBo> childList = new ArrayList<>();
                    for (SystemDictCacheBo childSystemDict : dictBos) {
                        if (input.getId()
                            .equals(childSystemDict.getParentId())) {
                            childList.add(childSystemDict);
                        }
                    }
                    input.setChildList(childList);
                }
            });
        }
        return dictBos;
    }

    @Override
    public List<SystemDictCacheBo> queryDictListByCache() {
        List<SystemDictCacheBo> cacheList = JSON.parseArray(dictCache.get(Constants.DICT_LIST_CACHE), SystemDictCacheBo.class);
        if(CollectionUtil.isNotEmpty(cacheList)){
            return cacheList;
        }
        cacheList = SystemDictConverter.doList2CacheBoList(systemDictDao.querySystemDictList());
        List<SystemDictCacheBo> dictBos = cacheList;
        if (cacheList != null && !cacheList.isEmpty()) {
            cacheList.forEach(input -> {
                String parentId = input.getParentId();
                if (StringUtils.isEmpty(parentId)) {
                    List<SystemDictCacheBo> childList = new ArrayList<>();
                    for (SystemDictCacheBo childSystemDict : dictBos) {
                        if (input.getId()
                            .equals(childSystemDict.getParentId())) {
                            childList.add(childSystemDict);
                        }
                    }
                    input.setChildList(childList);
                }
            });
        }
        dictCache.set(Constants.DICT_LIST_CACHE,JSON.toJSONString(cacheList));
        return cacheList;
    }

    @Override
    public Map<String,SystemDictCacheBo> getSystemDictByItemCodes(List<String> itemCodes) {
        Map<String,SystemDictCacheBo> resultMap = new HashMap<>();
        List<SystemDictCacheBo> systemDictBos = queryDictListByCache();
        if(CollectionUtil.isEmpty(systemDictBos)){
            return null;
        }
        Map<String, SystemDictCacheBo> map = systemDictBos.stream()
            .filter(systemDictBo -> StringUtil.isNotBlank(systemDictBo.getItemCode())).collect(
            Collectors.toMap(systemDictBo-> systemDictBo.getItemCode(),  systemDictBo-> systemDictBo));
        for(String itemCode : itemCodes){
            if(map.containsKey(itemCode)){
                resultMap.put(itemCode,map.get(itemCode));
            }
        }
        return resultMap;
    }
}
